﻿var _hy = _hy || {};
_hy.Chart = _hy.Chart || {};
_hy.Color = _hy.Color || {};

_hy.addEvent = function (obj, eventName, fn, useCapture) {
    if (obj == null) return false;
    useCapture = !useCapture ? false : true;
    if (obj.addEventListener) {
        return obj.addEventListener(eventName, fn, useCapture);
    } else if (obj.detachEvent) {
        eventName = "on" + eventName;
        return obj.attachEvent(eventName, fn);
    }
    return false;
};

_hy.GetEvent = function () {
    //同时兼容ie和ff的写法
    if (document.all) {
        var eArg = window.event;
        eArg.sender = eArg.srcElement || eArg.target;
        return eArg;
    }
    var func = _hy.GetEvent.caller;
    while (func != null) {
        var arg0 = func.arguments[0];
        if (arg0) {
            if ((arg0.constructor == Event || arg0.constructor == MouseEvent) || (typeof (arg0) == "object" && arg0.preventDefault && arg0.stopPropagation)) {
                arg0.sender = arg0.srcElement || arg0.target;
                return arg0;
            }
        }
        func = func.caller;
    }
    return null;
};
//解析模板。并将数据源中对应该的值填入。dataSource 是一个Array,rowsIndex 是索引值。
//模板格式为：<a href=''>#=Name# #=ar[0].Name#</a>
_hy.GetDataFromTemplet = function (str, rowsIndex, dataSource) {
    var reg = RegExp("#=[A-z0-9\.\(\)]{1,}#");
    var temp = str.match(reg);
    if (temp == null)
        return str;
    else {
        var tempField = temp[0].substr(2, temp[0].length - 3);
        var tempData = "";
        if (tempField == "CurrentIndex")
            tempData = rowsIndex;
        else {
            if (tempField.substr(0, 1) == '[') {
                tempData = eval("dataSource[" + rowsIndex + "]" + tempField);
            }
            else {
                tempData = eval("dataSource[" + rowsIndex + "]." + tempField);
            }
        }
        var str = str.replace(reg, tempData);
        return _hy.GetDataFromTemplet(str, rowsIndex, dataSource);
    }
}
_hy.Color.hexch = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F"];
_hy.Color.hexStr = "0123456789ABCDEF";
_hy.Color.baseColor = ["#000080", "#008080", "#800080", "#808000", "#00FF00", "#008000", "#800000", "#c0c0c0", "#ff00ff", "#808080", "#0000ff", "#00ffff", "#00ff00", "#ffff00", "#ff0000", "#000000", "#ffffff"];
_hy.Color.GetColorList = function (n) {
    var newColor;
    if (n <= 16) {
        newColor = _hy.Color.baseColor;
        return newColor;
    }
    newColor = new Array();
    var t = parseInt(255 / n) + 1;
    for (var i = 0; i < n; i++) {
        var r = Math.random() * 255;
        var g = Math.random() * 255;
        var b = Math.random() * 255;
        newColor[i] = _hy.Color.RGB2Color(r, g, b);
    }

    return newColor;
}

_hy.Color.ToHex = function (n) {
    var h, l;
    n = Math.round(n);
    l = n % 16;
    h = Math.floor((n / 16)) % 16;
    return (_hy.Color.hexch[h] + _hy.Color.hexch[l]);
}

_hy.Color.RGB2Color = function (r, g, b) {
    var r, g, b;
    return ('#' + _hy.Color.ToHex(r) + _hy.Color.ToHex(g) + _hy.Color.ToHex(b));
}

//#FFFFFF
_hy.Color.Color2RGB = function (strhex) {
    r = _hy.Color.hexStr.indexOf(strhex.charAt(1).toUpperCase()) * 16 + _hy.Color.hexStr.indexOf(strhex.charAt(2).toUpperCase());
    g = _hy.Color.hexStr.indexOf(strhex.charAt(3).toUpperCase()) * 16 + _hy.Color.hexStr.indexOf(strhex.charAt(4).toUpperCase());
    b = _hy.Color.hexStr.indexOf(strhex.charAt(5).toUpperCase()) * 16 + _hy.Color.hexStr.indexOf(strhex.charAt(6).toUpperCase());
    return { r: r, g: g, b: b };
}
_hy.GetLayerXY = function (ev) {
    if (ev.offsetX == undefined || ev.offsetY == undefined) {
        return { x: ev.layerX, y: ev.layerY };
    }
    return { x: ev.offsetX, y: ev.offsetY };
}
_hy.Point = function (x, y) {
    this.x = x;
    this.y = y;
}
_hy.Palette = function (id, panel, x, y, xmax, ymax) {
    this.id = id;
    this.x = x; //坐标系X轴
    this.y = y; //坐标系Y轴
    this.panel = panel;
    this.IsPrint = false;
    this.layer = new Array();
    this.g = new Array();
    //this.mmhandler = mousemovehandler;      //值：为string 方法名称，如："mouseMove"
    //this.mmoutHandler = onmouseOuthandler;  //值：为string 方法名称，如："mouseMove"
    this.backgroundcolor = "#fff333";
    this.reticleColor = "#00ff36";
    this.coordLineColor = "#E0E0E0";
    this.rowno = 5; //y轴刻度数
    this.cellno = 5; //x轴刻度数   
    this.xmax = xmax; //x轴最大刻度值
    this.ymax = ymax; //y轴最大刻度值
    this.yProportion = 0; //比列
    this.xProportion = 0;
    this.peak; //设置顶点；  
    this.IsShowYpoint = false;
    this.IsShowXpoint = true;

}

_hy.Palette.prototype.OnInit = function () {

    this.ymax = this.getmax(this.ymax); //y轴最大刻度值
    this.yProportion = this.y / this.ymax; //比列
    this.xProportion = this.x / this.xmax;
    //this.xProportion =5;   
    this.peak = new _hy.Point(0, this.ymax); //设置顶点；
    var htm = "<div id='" + this.id + "layer1' style='position: absolute;cursor: pointer;background-color:" + this.backgroundcolor + ";' ></div>";
    htm = htm + "<div id='" + this.id + "layer2' style='position: absolute;cursor: pointer;'></div>";
    //    var onmousemoveStr = "", onmouseoutStr = "";
    //    if (this.mmhandler != undefined) {
    //        onmousemoveStr = "onmousemove='" + this.mmhandler + "(event);'";
    //    }

    //    if (this.mmoutHandler != undefined) {
    //        onmouseoutStr = "onmouseout = '" + this.mmoutHandler + "();'";
    //    }
    htm = htm + "<div id='" + this.id + "layer3' style='position: absolute;cursor: pointer;overflow:auto;'></div>";

    this.panel.innerHTML = htm;
    this.layer[0] = document.getElementById(this.id + "layer1");
    this.layer[1] = document.getElementById(this.id + "layer2");
    this.layer[2] = document.getElementById(this.id + "layer3");
    this.panel.style.width = (this.x) + "px";
    this.panel.style.height = (this.y) + "px";
    this.layer[0].style.width = (this.x) + "px";
    this.layer[0].style.height = (this.y) + "px";
    this.layer[1].style.width = (this.x) + "px";
    this.layer[1].style.height = (this.y) + "px";
    this.layer[2].style.width = (this.x) + "px";
    this.layer[2].style.height = (this.y) + "px";
    this.g[0] = new jsGraphics(this.layer[0]);
    this.g[1] = new jsGraphics(this.layer[1]);
    this.g[2] = new jsGraphics(this.layer[2]);
    this.OnMouseMove = function (self) {
        ev = _hy.GetEvent();
        var srcobj = ev.srcElement ? ev.srcElement : ev.target;
        this.g[0].setFont("宋体", "13px", Font.BOLD);

        if (this.layer[2] == srcobj) {
            ev = _hy.GetLayerXY(ev);
            var po = this.atov(ev.x, ev.y);
            this.g[0].clear();
            this.g[0].setColor(this.reticleColor);
            if (this.IsShowXpoint)
                if (po.y > 0 && po.y < this.ymax)
                    this.g[0].fillRect(0, ev.y, this.x, 1);
            if (this.IsShowYpoint)
                if (po.x > 0 && po.x < this.xmax)
                     this.g[0].fillRect(ev.x, 0, 1, this.y);
            this.g[0].setColor("#000000");
            if (this.IsShowXpoint) {
                if (po.y > 0 && po.y < this.ymax)
                    this.g[0].drawStringRect(po.y, this.x + 5, ev.y - 6, 50, "left");
            }
            if (this.IsShowYpoint)
                if (po.x > 0 && po.x < this.xmax)
                    this.g[0].drawStringRect(po.x, ev.x - 25, -20, 50, "center");
            this.g[0].paint();
        }
        else {
            var left = srcobj.style.left;
            var top = srcobj.style.top;
            ev = _hy.GetLayerXY(ev);
            var top = parseInt(top.substring(0, top.length - 2));
            var po = this.atov(ev.x, ev.y + top);
            po.x = ev.x + parseInt(left.substring(0, left.length - 2));
            this.g[0].clear();
            this.g[0].setColor(this.reticleColor);
            var point = this.vtoa(po.x, po.y);
            if (this.IsShowXpoint)
                if(po.y >0 && po.y<this.ymax)
                    this.g[0].fillRect(0, ev.y + top, this.x, 1);
            if (this.IsShowYpoint)
                if (po.x > 0 && po.x < this.xmax)
                    this.g[0].fillRect(po.x, 0, 1, this.y);
            this.g[0].setColor("#000000");
            if (this.IsShowXpoint)
                if (po.y > 0 && po.y < this.ymax)
                this.g[0].drawStringRect(po.y, this.x + 5, point.y - 6, 50, "left");
            if (this.IsShowYpoint)
                if (po.x > 0 && po.x < this.xmax)
                    this.g[0].drawStringRect(po.x, po.x - 25, -20, 50, "center");
            this.g[0].paint();
        }
    };
    this.OnMouseOut = function (self) { this.g[0].clear(); };
    _hy.addEvent(this.layer[2], "mousemove", (function (v) { return function () { v.OnMouseMove(v); }; })(this)); //事件传递参数
    _hy.addEvent(this.layer[2], "mouseout", (function (v) { return function () { v.OnMouseMove(v); }; })(this));
}
_hy.Palette.prototype.paint = function () {
    this.OnInit();
    this.g[0].setPrintable(this.IsPrint);
    this.g[1].setPrintable(this.IsPrint);
    this.g[2].setPrintable(this.IsPrint);
    this.rh = this.y / this.rowno; //每行高度
    this.g[1].setFont("宋体", "12px", Font.BOLD);
    this.g[1].setColor(this.coordLineColor);
    this.g[1].fillRect(0, 0, 1, this.y);
    for (var i = 0; i <= this.rowno; i++) {
        this.g[1].setColor(this.coordLineColor);
        this.g[1].fillRect(0, i * this.rh, this.x, 1);
        this.g[1].setColor("#000000");
        this.g[1].drawStringRect(this.ymax - (i * this.ymax / this.rowno), -105, i * this.rh - 12, 100, "right");
    }
    this.g[1].setColor(this.coordLineColor);
    this.g[1].fillRect(this.x, 0, 1, this.y);
    this.g[1].paint();

}

_hy.Palette.prototype.vtoa = function (x, y) {
    var point = new _hy.Point(x, y);
    point.x = (this.peak.x + x) * this.xProportion;
    point.y = (this.peak.y - y) * this.yProportion;
    return point;
}

_hy.Palette.prototype.getwh = function (x, y) {
    var point = new _hy.Point(x, y);
    point.x = (x) * this.xProportion;
    point.y = (y) * this.yProportion;
    return point;
}

_hy.Palette.prototype.atov = function (x, y) {
    var point = new _hy.Point(x, y);
    point.x = Math.ceil((x) / this.xProportion);
    point.y = Math.ceil((this.y - y) / this.yProportion);
    return point;
}
//计算最大坐标系
_hy.Palette.prototype.getmax = function (ymax) {
    var idiv_0 = ymax / this.rowno;
    var imod = idiv_0 % 10;
    if (imod == 0) return ymax;
    var idiv = parseInt(ymax / this.rowno);
    var ilen = idiv.toString(10).length;
    if (ilen < 2) {
        ymax = (idiv + 1) * this.rowno;
        return ymax;
    }
    var ilen_2 = parseInt(ilen / 2);
    if (ilen_2 == 0) {
        return ymax;
    }
    var bf = idiv.toString(10).substr(0, ilen - ilen_2);
    var ibf = parseInt(bf) + 1;
    var tp = "";
    for (var i = 0; i < ilen_2; i++) {
        tp = tp + "0";
    }
    tp = ibf + tp;
    return parseInt(tp) * this.rowno;
}

//线性图
_hy.Chart.Line = function (palette) {
    this.p = palette;
    this.DataSource;
    this.ColorList;
    this.attr = "";
    this.InfoPanel;
    this.lineStyle = "";
    this.IsShowXstr = true;
    this.IsShowValue = true;

}
_hy.Chart.Line.prototype.setDataSource = function (valueArr) {
    this.DataSource = valueArr;
    this.DataSource.row = valueArr.length;
    this.DataSource.cell = valueArr[0].length;
    this.ColorList = _hy.Color.GetColorList(valueArr[0].length);
}
_hy.Chart.Line.prototype.showInfo = function () {
    if (this.InfoPanel == null) {
        alert(_hy.Message.War01);
        return;
    }
    var cell = this.DataSource.cell - 2;
    var htmstr = "";
    for (var i = 0; i < cell; i++) {
        htmstr = htmstr + "<div style='color: " + this.ColorList[i] + ";'>■ " + this.DataSource[0][i + 1] + " </div>";
    }
    this.InfoPanel.innerHTML = htmstr;
}
_hy.Chart.Line.prototype.paint = function (xProportion) {
    var d = this.DataSource;
    if (this.IsShowXstr) {
        this.p.layer[2].style.height = (this.p.y + 50) + "px";
        this.p.xProportion = (d[1][0].length * 22) / 2;
    }
    else {
        this.p.layer[2].style.height = (this.p.y + 20) + "px";

    }
    if (xProportion != null) {
        this.p.xProportion = xProportion;
    }
    if (this.p.xProportion < ((d[1][0].length * 22) / 2)) {
        this.p.layer[2].style.height = (this.p.y + 20) + "px";
        this.IsShowXstr = false;
    }
    else {
        this.p.layer[2].style.height = (this.p.y + 50) + "px";
        this.IsShowXstr = true;
    }
    this.p.g[2].clear();
    var cellw = this.p.xmax / (d.row);
    for (var i = 1; i < (d.row); i++) {
        this.p.g[2].setColor(this.p.coordLineColor);
        var point = this.p.vtoa(i * cellw, 0);
        this.p.g[2].fillRect(point.x, 0, 1, point.y);
        if (this.IsShowXstr) {
            this.p.g[2].setColor("#000000");
            this.p.g[2].drawStringRect(this.DataSource[i][0], point.x - (d[i][0].length * 22) / 2, point.y + 10, (d[i][0].length * 22), "center");
        }
    }
    this.p.g[2].paint();
    var pointsX = new Array(d.cell);
    var pointsY = new Array(d.cell);
    for (var i = 0; i < d.cell - 2; i++) {
        pointsX[i] = new Array(d.row - 2);
        pointsY[i] = new Array(d.row - 2);
    }
    this.p.g[2].setStyle(this.lineStyle);
    for (var i = 1; i < d.length; i++) {
        if (this.attr != "") {
            this.p.g[2].setAttr(_hy.GetDataFromTemplet(this.attr, i, this.DataSource));
        }
        for (var j = 1; j < d.cell - 1; j++) {
            var point = this.p.vtoa(i * cellw, d[i][j]);
            this.p.g[2].setColor(this.ColorList[j - 1]);
            if (this.IsShowValue) {
                this.p.g[2].drawStringRect(d[i][j], point.x - 3, point.y - 3 - 15, 50, "left");
            }
            this.p.g[2].fillRect(point.x - 3, point.y - 3, 6, 6);
            pointsX[j - 1][i - 1] = point.x;
            pointsY[j - 1][i - 1] = point.y;
        }
        this.p.g[2].paint();
    }
    this.p.g[2].setAttr("");
    for (var i = 0; i < d.cell - 2; i++) {
        this.p.g[2].setColor(this.ColorList[i]);
        this.p.g[2].setStroke(1);
        this.p.g[2].drawPolyline(pointsX[i], pointsY[i]);
    }
    this.p.g[2].paint();
}

//柱状图
_hy.Chart.Bar = function (palette) {
    this.p = palette;
    this.DataSource;
    this.ColorList;
    this.attr = "";
    this.InfoPanel;
    this.barStyle = "";
    this.attr = "";
    this.IsShowXstr = true;
    this.IsShowValue = true;
}
_hy.Chart.Bar.prototype.setDataSource = function (valueArr) {
    this.DataSource = valueArr;
    this.DataSource.row = valueArr.length;
    this.DataSource.cell = valueArr[0].length;
    this.ColorList = _hy.Color.GetColorList(valueArr[0].length);
}
_hy.Chart.Bar.prototype.paint = function (xProportion) {
    this.p.g[2].clear();
    var d = this.DataSource;
    if (xProportion != null) {
        this.p.xProportion = xProportion;
    }
    var cellw = this.p.xmax / (d.row);
    var cellNo = d.cell - 2; //柱子数目。
    var cellNow = cellw / (cellNo + 1);
    for (var i = 1; i < (d.row); i++) {
        this.p.g[2].setColor(this.p.coordLineColor);
        var point = this.p.vtoa(i * cellw, 0);
        this.p.g[2].fillRect(point.x, 0, 1, point.y);
        if (this.IsShowXstr) {
            this.p.g[2].setColor("#000000");
            this.p.g[2].drawStringRect(d[i][0], point.x - 25, point.y + 10, 50, "center");
        }
    }
    this.p.g[2].paint();
    this.p.g[2].setStyle(this.barStyle);

    var startPointv = new _hy.Point(cellw / 2, 0);

    for (var i = 1; i < d.length; i++) {
        if (this.attr != "") {
            //alert(this.MouseMoveHandler);
            this.p.g[2].setAttr(_hy.GetDataFromTemplet(this.attr, i, this.DataSource));
        }
        startPointv.x = startPointv.x + (cellNow / 2);
        for (var j = 1; j < d.cell - 1; j++) {
            var point = this.p.vtoa(startPointv.x, d[i][j]);
            var wh = this.p.getwh(cellNow, d[i][j]);
            this.p.g[2].setColor(this.ColorList[j - 1]);

            this.p.g[2].fillRect(point.x, point.y, wh.x, wh.y);
            if (this.IsShowValue) {
                this.p.g[2].drawStringRect(d[i][j], point.x, point.y - 3 - 17, 50, "left");
            }
            startPointv.x = startPointv.x + (cellNow);
        }
        startPointv.x = startPointv.x + (cellNow / 2);
        this.p.g[2].paint();

    }

    this.p.g[2].paint();
}

_hy.Chart.Bar.prototype.showInfo = function () {
    if (this.InfoPanel == null) {
        alert("请在调用ShowInfo()之前，设置InfoPanel属性。");
        return;
    }
    var cell = this.DataSource.cell - 2;
    var htmstr = "";
    for (var i = 0; i < cell; i++) {
        htmstr = htmstr + " <div style='color: " + this.ColorList[i] + ";'>■ " + this.DataSource[0][i + 1] + " </div>";
    }
    this.InfoPanel.innerHTML = htmstr;
}
//柄状图
_hy.Chart.Pie = function (palette) {
    this.p = palette;
    this.DataSource;
    this.ColorList;
    this.attr = "";
    this.InfoPanel;
    this.lineStyle = "";
    this.dataSum = 0; //计算总数。
    this.pieStyle = "";
    this.IsShowValue = false;
    this.Algorithm = null;
}

_hy.Chart.Pie.prototype.setDataSource = function (valueArr) {
    this.DataSource = valueArr;
    this.DataSource.row = valueArr.length;
    //this.DataSource.cell = valueArr.length - 1;
    this.ColorList = _hy.Color.GetColorList(valueArr.length - 1);
}
_hy.Chart.Pie.prototype.paint = function () {
    var d = this.DataSource;
    var peak = new _hy.Point(this.p.xmax / 2, this.p.ymax / 2);

    var point = this.p.vtoa(peak.x, 0);
    //this.p.g[1].fillRect(point.x,0,1,point.y);
    this.p.g[1].setColor("#000000");
    this.p.g[1].drawStringRect(d[0][1], point.x - (this.p.x / 2) / 2, point.y + 10, this.p.x / 2, "center");
    this.p.g[1].setColor(this.p.coordLineColor);
    this.p.g[1].paint();
    var arc = 360 / d.length - 1;
    if (this.dataSum == 0) {
        for (var i = 1; i < d.length; i++) {
            this.dataSum = this.dataSum + d[i][1];
        }
    }
    var peakA = this.p.vtoa(peak.x, peak.y);
    var startArc = 0;
    var endArc = 0;
    this.p.g[2].setStyle(this.pieStyle);
    for (var i = 1; i < d.length; i++) {
        if (this.attr != "") {
            //alert(this.MouseMoveHandler);
            this.p.g[2].setAttr(_hy.GetDataFromTemplet(this.attr, i, this.DataSource));
        }

        var percentage = 0;
        if (this.Algorithm == null) {
            percentage = d[i][1] / this.dataSum;
        }
        else {
            percentage = this.Algorithm(i);
        }

        if (percentage != 0) {
            endArc = startArc + (percentage * 360);
            this.p.g[2].setColor(this.ColorList[i - 1]);
            var peakB = new _hy.Point(peakA.x - ((this.p.x * (2 / 3)) / 2), peakA.y - ((this.p.y - 20) / 2));
            var whB = new _hy.Point((this.p.x * (2 / 3)), this.p.y - 20);
            this.p.g[2].fillArc(peakB.x, peakB.y, whB.x, whB.y, startArc, endArc);

            this.p.g[2].setColor("#000000");
            var arc = startArc + ((endArc - startArc) / 2);
            var num = (d[i][1] / this.dataSum) * 100;

            var strx = (whB.x / 2 + 5) * Math.cos((Math.PI / 180) * -arc);
            var stry = (whB.y / 2 + 5) * Math.sin((Math.PI / 180) * -arc);
            if (this.IsShowValue)
                this.p.g[2].drawString(num.toFixed(2) + "%", strx + (this.p.x / 2), stry + (this.p.y / 2));

            startArc = endArc;
            this.p.g[2].paint();
        }
    }
}
_hy.Chart.Pie.prototype.showInfo = function () {
    if (this.InfoPanel == null) {
        alert(_hy.Message.War01);
        return;
    }
    var d = this.DataSource;
    var htmstr = "";
    for (var i = 1; i < d.length; i++) {
        var num = (d[i][1] / this.dataSum) * 100;
        htmstr = htmstr + "<div style='color: " + this.ColorList[i - 1] + ";'><span style='border: 1px solid #000000; line-height:20px; background-color:" + this.ColorList[i - 1] + ";'>&nbsp;&nbsp;</span> <span style='color:#000000;'>" + d[i][0] + " " + num.toFixed(2) + "%</span>" + " </div>";
    }
    this.InfoPanel.innerHTML = htmstr;
}



   